package com.logic.system.service.impl;

import com.logic.common.ErrorMessageEnum;
import com.logic.common.exception.BusinessException;
import com.logic.common.security.SecurityUtils;
import com.logic.common.util.QueryUtil;
import com.logic.common.util.SysUtil;
import com.logic.common.ws.dto.configuration.UserEmployeeDTO;
import com.logic.common.ws.dto.system.UserDTO;
import com.logic.common.ws.dto.system.UserPassChangeDTO;
import com.logic.common.ws.dto.system.UserSearchDTO;
import com.logic.landseaserver.common.config.SendMsgConfiguration;
import com.logic.landseaserver.common.enums.RoleTypeEnum;
import com.logic.landseaserver.common.enums.SendMsgCodeEnum;
import com.logic.landseaserver.common.exception.LandseaBusinessException;
import com.logic.landseaserver.common.exception.WechatBusinessException;
import com.logic.landseaserver.common.util.DESUtil;
import com.logic.landseaserver.common.util.SMSUtil;
import com.logic.landseaserver.domain.VerificationCode;
import com.logic.landseaserver.domain.WeChatUserLogin;
import com.logic.landseaserver.persistence.write.WeChatUserLoginWriteMapper;
import com.logic.landseaserver.service.ISendSmsService;
import com.logic.landseaserver.ws.dto.UserPrjRoleDTO;
import com.logic.landseaserver.ws.request.RegisterReq;
import com.logic.system.domain.*;
import com.logic.system.persistence.read.OrganizationReadMapper;
import com.logic.system.persistence.read.RoleReadMapper;
import com.logic.system.persistence.read.UserReadMapper;
import com.logic.system.persistence.write.UserWriteMapper;
import com.logic.system.service.*;
import com.logic.system.ws.dto.UserConverter;
import org.apache.commons.lang.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.bind.RelaxedPropertyResolver;
import org.springframework.context.EnvironmentAware;
import org.springframework.core.env.Environment;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.Assert;
import org.springframework.util.CollectionUtils;

import javax.servlet.http.HttpServletRequest;
import java.io.UnsupportedEncodingException;
import java.sql.Timestamp;
import java.util.*;

/**
 * <p>
 * Title: UserService
 * </p>
 * <p>
 * <p>
 * Description: 用户管理服务
 * </p>
 * <p>
 * <p>
 * Company: Logicsolutions
 * </p>
 *
 * @author gary.wang@logicsolutions.com.cn
 * @date 2014-8-6FF
 */
@Service
public class UserService implements IUserService, EnvironmentAware {

    private static final Logger logger = LoggerFactory.getLogger(UserService.class);

    private static final String USER_NAME_PREFIX = "TUSER-";
    private static final String ENV_FILE_PATH = "logic.file.path.";
    private static final String LOCAL_PATH = "local";
    private static final String REMOTE_PATH = "remote";

    private static RelaxedPropertyResolver propertyResolver;

    @Autowired
    OrganizationReadMapper orgReadMapper;

    @Autowired
    WeChatUserLoginWriteMapper weChatUserLoginWriteMapper;

    @Autowired
    IWeChatService weChatService;

    @Autowired
    private UserReadMapper userReadMapper;


    @Autowired
    private UserWriteMapper userWriteMapper;

    @Autowired
    private PersonalInfoService personalInfoService;

//  @Autowired
//  private SystemClient systemClient;

    @Autowired
    private RoleReadMapper roleReadMapper;

//  @Autowired
//  private IEmployeeService employeeService;

    @Autowired
    private HttpServletRequest request;

    @Autowired
    ICodeService codeService;

    @Autowired
    ITaskService taskService;

    @Autowired
    IConfigurationService configurationService;

    @Autowired
    private SendMsgConfiguration sendMsgConfiguration;

    @Autowired
    private ISendSmsService sendSmsService;

    /**
     * Retrieve user object by user ID.
     *
     * @param id
     * @return
     * @throws BusinessException TODO
     */
    public User get(Integer id) throws BusinessException {
        User user = userReadMapper.selectByPrimaryKey(id);

        if (user != null) {

            if (user.getPersonalInfoId() != null) {
                PersonalInfo personalInfo = personalInfoService.get(user.getPersonalInfoId());
                user.setPersonalInfo(personalInfo);
            }

            List<UserOrg> userOrgs = userReadMapper.selectOrgByUserId(id);
            if (userOrgs != null && userOrgs.size() != 0) {
                user.setUserOrgs(userOrgs);
            }

            List<UserArea> userAreas = userReadMapper.selectAreaByUserId(id);
            if (userAreas != null && userAreas.size() != 0) {
                user.setUserAreas(userAreas);
            }

            List<UserProject> userProject = userReadMapper.selectProjectByUserId(id);
            if (userProject != null && userProject.size() != 0) {
                user.setUserProjects(userProject);
            }

            if (user.getId() != null) {
                List<Role> roleList = roleReadMapper.getRolesByUserID(id);
                user.setRoleList(roleList);
            }
        }

        return user;
    }

    @Autowired
    private OrganizationReadMapper organizationReadMapper;

    @Override
    public List<Organization> getUserOrganizations(Integer userId) {
        Assert.notNull(userId);
        List<UserOrg> userOrgs = userReadMapper.selectOrgByUserId(userId);

        if (CollectionUtils.isEmpty(userOrgs)) return null;

        List<Organization> organizations = new ArrayList<>();
        for (UserOrg userOrg : userOrgs) {
            Organization organization = organizationReadMapper.selectByPrimaryKey(userOrg.getOrgId());
            if (organization != null) organizations.add(organization);
        }

        return organizations;
    }

    @Override
    public User getByLoginId(String loginId) {
//    User user = (User) SysCache.getInstance().getCacheItem(USER_NAME_PREFIX + loginId);
//    if (user == null){
//      user = userReadMapper.selectByLoginId(loginId);
//    }
//
//    if (user != null){
//      SysCache.getInstance().setCacheItem(USER_NAME_PREFIX + loginId, user);
//    }

        User user = userReadMapper.selectByLoginId(loginId);

        return user;
    }

    @Override
    public List<Role> getRolesByUserId(Integer userId) {
        return roleReadMapper.getRolesByUserID(userId);
    }

    @Override
    public List<UserRole> getUserRolesByUserId(Integer userId) {
        return userReadMapper.getUserRolesByUserId(userId);
    }

    @Transactional(propagation = Propagation.SUPPORTS, rollbackFor = {BusinessException.class, Exception.class})
    public int insert(Object obj) throws BusinessException {
        UserDTO userDTO = (UserDTO) obj;
        User user = UserConverter.fromDTOtoUser(userDTO);

        //change user login
        if (StringUtils.isNotBlank(user.getLoginId())) {
            user.setLoginId(user.getLoginId().toLowerCase());
        }

        Integer employeeId = null;
        if (null != userDTO.getEmployee_id() && !StringUtils.isEmpty(userDTO.getEmployee_id())) {
            employeeId = Integer.parseInt(userDTO.getEmployee_id());
        }

        boolean isValidUserForInsert = this.validateForInsert(user);
        if (isValidUserForInsert) {
            PersonalInfo personalInfo = user.getPersonalInfo();
            if (personalInfo != null) {
                Integer personalInfoId = personalInfoService.insert(personalInfo);
                user.setPersonalInfoId(personalInfoId);
            }

            user.setPassword(SysUtil.MD5Digest(user.getPassword()));

            if (canPWDExpired() && !StringUtils.isBlank(user.getPassword())) {
                user.setPwdExpiredDate(getPWDExpiredDate());
            }

            user.updateCommonInfo(SecurityUtils.getCurrentLogin().getUserId());
            userWriteMapper.insertSelective(user);

            insertUserRoles(user);
            insertUserAreas(user);
            insertUserProject(user);


            List<UserOrg> orgUsers = user.getUserOrgs();
            if (orgUsers != null && orgUsers.size() != 0) {
                for (UserOrg orgUser : orgUsers) {
                    orgUser.setUserId(user.getId());
                    userWriteMapper.insertUserOrgSelective(orgUser);
                }
            }
        }
        //插入微信端用户名密码
        WeChatUserLogin record = new WeChatUserLogin();
        record.setUsername(userDTO.getLogin_id());
        String password = "123456";
        try {
            record.setPassword(DESUtil.encrypt(password));
        } catch (UnsupportedEncodingException e) {
            logger.error("insert error.", e);
        }
        int a = weChatUserLoginWriteMapper.insert(record);

        return user.getId();
    }

    private void insertUserRoles(User user) {
        List<Role> roles = user.getRoleList();
        if (roles != null && roles.size() > 0) {
            List<UserRole> userRoles = new ArrayList<UserRole>();
            for (int i = 0; i < roles.size(); i++) {
                UserRole userRole = new UserRole();
                userRole.setUserId(user.getId());

                int roleId = roles.get(i).getId();
                userRole.setRoleId(roleId);
                userRoles.add(userRole);
            }

            userWriteMapper.insertUserRoles(userRoles);
        }
    }

    private void insertUserAreas(User user) {
        List<UserArea> areas = user.getUserAreas();
        if (areas != null && areas.size() > 0) {

            for (int i = 0; i < areas.size(); i++) {
                UserArea area = areas.get(i);
                area.setUserId(user.getId());
            }
            userWriteMapper.insertUserAreas(areas);
        }
    }

    private void insertUserProject(User user) {
        List<UserProject> projs = user.getUserProjects();
        if (projs != null && projs.size() > 0) {

            for (int i = 0; i < projs.size(); i++) {
                UserProject project = projs.get(i);
                project.setUserId(user.getId());
                project.setPrjRole("PRRO4");
                project.setVersion(0);
                project.setDeleted(false);
                project.setCreatedDtm( new Timestamp((new Date()).getTime()));
                project.setCreatedBy(SecurityUtils.getCurrentLogin().getUserId());
            }
            userWriteMapper.insertUserProjects(projs);
        }
    }

    @Transactional(propagation = Propagation.SUPPORTS, rollbackFor = {BusinessException.class, Exception.class})
    public void update(Object obj) throws BusinessException {
        UserDTO userDTO = (UserDTO) obj;
        User user = UserConverter.fromDTOtoUser(userDTO);

        if (validateForUpdate(user)) {
            Integer employeeId = null;
            if (null != userDTO.getEmployee_id() && !StringUtils.isEmpty(userDTO.getEmployee_id().toString())) {
                employeeId = Integer.parseInt(userDTO.getEmployee_id());
            }

            // Update User Object itself
            User systemUser = get(user.getId());
            if (systemUser == null) {
                throw new BusinessException(ErrorMessageEnum.User_UpdateUser_User_Not_Exist, user.getId());
            }

            // Update Personal Information
            PersonalInfo personalInfo = user.getPersonalInfo();
            if (personalInfo != null) {
                Integer personalInfoId = systemUser.getPersonalInfoId();
                if (personalInfoId == null) {
                    personalInfoId = personalInfoService.insert(personalInfo);
                    user.setPersonalInfoId(personalInfoId);
                } else {
                    personalInfo.setId(personalInfoId);
                    personalInfoService.update(personalInfo);
                }
            }

            if (user.getPassword() != null && !user.getPassword().equals("")) {
                user.setPassword(SysUtil.MD5Digest(user.getPassword()));
                if (canPWDExpired()) {
                    user.setPwdExpiredDate(getPWDExpiredDate());
                }
            }

            user.updateCommonInfo(SecurityUtils.getCurrentLogin().getUserId());
            userWriteMapper.updateByPrimaryKeySelective(user);

            List<UserOrg> userOrgs = user.getUserOrgs();
            if (userOrgs != null) {
                if (userOrgs.isEmpty()) {
                    userWriteMapper.deleteUserOrgByUserId(user.getId());
                } else {
                    userWriteMapper.deleteUserOrgByUserId(user.getId());
                    for (UserOrg userOrg : userOrgs) {
                        userOrg.setUserId(user.getId());
                        userWriteMapper.insertUserOrgSelective(userOrg);
                    }
                }
            }

            List<UserArea> userAreas = user.getUserAreas();
            if (userAreas != null) {
                if (userAreas.isEmpty()) {
                    userWriteMapper.deleteUserAreaByUserId(user.getId());
                } else {
                    userWriteMapper.deleteUserAreaByUserId(user.getId());
                    for (UserArea userArea : userAreas) {
                        userArea.setUserId(user.getId());
                        userWriteMapper.insertUserAreaSelective(userArea);
                    }
                }
            }

            List<UserProject> userProjects = user.getUserProjects();
            if (userProjects != null) {
                if (userProjects.isEmpty()) {
                    UserProject up = new UserProject();
                    up.setUserId(user.getId());
                    up.setPrjRole(RoleTypeEnum.PRRO4.getCode());
                    up.updateCommonInfo(SecurityUtils.getCurrentLogin().getUserId());
                    up.setDeleted(true);
                    userWriteMapper.updateUserProjectBySelective(up);
                } else {
                    //删除已经存在的关系
                    UserProject up = new UserProject();
                    up.setUserId(user.getId());
                    up.setPrjRole(RoleTypeEnum.PRRO4.getCode());
                    up.updateCommonInfo(SecurityUtils.getCurrentLogin().getUserId());
                    up.setDeleted(true);
                    userWriteMapper.updateUserProjectBySelective(up);

                    UserProject param = new UserProject();
                    param.setUserId(user.getId());
                    List<UserProject> oldList = userReadMapper.selectProjectBySelective(param);
                    //取交集修改为deleted=0
                    List<UserProject> reulst = retainAll(userProjects, oldList);
                    for (UserProject userProject : reulst) {
                        userProject.updateCommonInfo(SecurityUtils.getCurrentLogin().getUserId());
                        userProject.setDeleted(false);
                        userWriteMapper.updateUserProjectBySelective(userProject);
                    }
                    //取差集做list
                    removeAll(userProjects, oldList);
                    for (UserProject userProject : userProjects) {
                        userProject.setUserId(user.getId());
                        userProject.setPrjRole("PRRO4");
                        userProject.updateCommonInfo(SecurityUtils.getCurrentLogin().getUserId());
                        userWriteMapper.insertUserProjectSelective(userProject);
                    }
                }
            }

            // Update the relationship between user and role
            if (null != user.getRoleList()) {
                userWriteMapper.deleteUserRoles(user.getId());
                if (!user.getRoleList().isEmpty()) {
                    insertUserRoles(user);
                }
            }
        }

    }

    /**
     *
     * @param c 新的项目
     * @param c2 旧的项目
     * @return
     */
    public List<UserProject> retainAll(List<UserProject> c, List<UserProject> c2) {
        Objects.requireNonNull(c);
        Objects.requireNonNull(c2);
        List<UserProject> result = new ArrayList<UserProject>();
        boolean modified = false;
        Iterator it = c.iterator();
        while (it.hasNext()) {
            UserProject u1 = (UserProject) it.next();
            for (UserProject u2 : c2) {
                if (u1.getPrjId().intValue() == u2.getPrjId().intValue()) {
                    result.add(u1);
                    break;
                }
            }
        }
        return result;
    }

    public void removeAll(List<UserProject> c, List<UserProject> c2) {
        Objects.requireNonNull(c);
        Objects.requireNonNull(c2);
        List<UserProject> result = new ArrayList<UserProject>();
        boolean modified = false;
        Iterator it = c.iterator();
        while (it.hasNext()) {
            UserProject u1 = (UserProject) it.next();
            for (UserProject u2 : c2) {
                if (u1.getPrjId().intValue() == u2.getPrjId().intValue()) {
                    it.remove();
                    break;
                }
            }
        }
    }

    @Transactional
    public void delete(String ids) throws BusinessException {
        String[] idArr = ids.split(",");
        for (String id : idArr) {
            User systemUser = get(Integer.valueOf(id));
            if (systemUser == null) {
                throw new BusinessException(ErrorMessageEnum.User_DeleteUser_User_Not_Exist, Integer.valueOf(id));
            }
            userWriteMapper.deleteUserRoles(Integer.valueOf(id));
            User user = get(Integer.valueOf(id));
            PersonalInfo personalInfo = user.getPersonalInfo();

            if (personalInfo != null) {
                personalInfoService.deletePersonalInfo(personalInfo);
            }

            user.updateCommonInfo(SecurityUtils.getCurrentLogin().getUserId());
            userWriteMapper.deleteByPrimaryKey(user);
            userWriteMapper.deleteUserOrgByUserId(user.getId());
        }
    }

    public List<Object> query(QueryUtil queryUtil) {
        List<Object> list = new ArrayList<Object>();
        List<UserDTO> dtos = userReadMapper.selectUsers(queryUtil);
        String url = propertyResolver.getProperty(REMOTE_PATH, String.class, null);
        if (dtos != null) {
            for (UserDTO dto : dtos) {
                dto.setPassword("");
                dto.setLocked("1".equals(dto.getLocked()) ? "true" : "false");
                dto.setDisabled("1".equals(dto.getDisabled()) ? "true" : "false");

                if (dto.getAvatar() != null) {
                    if (!dto.getAvatarFileName().contains("_")) {
                        dto.setAvatar(url + "/" + dto.getAvatarFileName());
                    } else {
                        dto.setAvatar(url + "/" + dto.getAvatarFileName().substring(0, dto.getAvatarFileName().indexOf("_")));
                    }
                }
                list.add(dto);
            }
        }
        return list;
    }

    public Boolean validateForInsert(Object obj) throws BusinessException {

        logger.debug("===========Start Valid User Object");

        boolean ret = validate(obj);
        User user = (User) obj;

        if (null != user.getId()) {
            throw new BusinessException(ErrorMessageEnum.User_CreateUser_Empty_ID);
        }

        if (StringUtils.isEmpty(user.getLoginId())) {
            throw new BusinessException(ErrorMessageEnum.User_CreateUser_Empty_LoginID);
        }

        if (StringUtils.isEmpty(user.getPassword())) {
            throw new BusinessException(ErrorMessageEnum.User_CreateUser_Empty_Password);
        }

        if (null == user.getDisabled()) {
            throw new BusinessException(ErrorMessageEnum.User_CreateUser_Empty_Disabled);
        }

        if (null == user.getLocked()) {
            throw new BusinessException(ErrorMessageEnum.User_CreateUser_Empty_Locked);
        }

//    if (StringUtils.isEmpty(user.getPersonalInfo().getEmailPrimary())) {
//      throw new BusinessException(ErrorMessageEnum.User_CreateUser_Empty_Email);
//    }


        ret = true;

        logger.debug("===========End Valid User Object");

        return ret;
    }

    // We do not need login any further since we will be using OAuth2
//  public String login(LoginDTO dto) throws BusinessException {
//    String token = "";
//    String userName = dto.getUserName();
//    String password = dto.getPassword();
//
//    if (StringUtils.isEmpty(userName) || StringUtils.isEmpty(password)) {
//      throw new BusinessException(ErrorMessageEnum.Permiss_Login_Empty_Username_Or_Password);
//    } else {
//      User user = userReadMapper.selectByLoginId(userName);
//      if (user != null) {
//  List<UserOrg> userOrgs = userReadMapper.selectOrgByUserId(user.getId());
//  List<String> orgIds = new ArrayList<String>();
//  if (userOrgs != null && userOrgs.size() != 0) {
//    user.setUserOrgs(userOrgs);
//    for (UserOrg userOrg : userOrgs) {
//      orgIds.add(userOrg.getOrgId().toString());
//    }
//  }
//        String pass = user.getPassword();
//        if (SysUtil.MD5Digest(password).equals(pass)) {
//          token = generateToken();
//
//          UserCacheDTO userCacheDto = new UserCacheDTO();
//          userCacheDto.setUserId(user.getId());
//          userCacheDto.setDefaultLocale(user.getDefaultLocale());
//          userCacheDto.setExpirationTime(System.currentTimeMillis() + 30 * 60 * 1000);
//          userCacheDto.setOrgId(SysUtil.listToSortedString(orgIds));
//
//          Integer personalInfoId = user.getPersonalInfoId();
//          PersonalInfo personalInfo = (PersonalInfo) personalInfoService.get(personalInfoId);
//          if (personalInfo != null) {
//            String firstName = personalInfo.getFirstName() == null ? "" : personalInfo.getFirstName();
//            String lastName = personalInfo.getLastName() == null ? "" : personalInfo.getLastName();
//            String name = firstName + " " + lastName;
//            userCacheDto.setUserName(name);
//          }
//
//          ICache cache = CacheFactory.getCacheImpl();
//          cache.setSession(token, userCacheDto);
//
//        } else {
//          throw new BusinessException(ErrorMessageEnum.Permiss_Login_Password_Is_Wrong);
//        }
//      } else {
//        throw new BusinessException(ErrorMessageEnum.Permiss_Login_Username_Not_Exist, userName);
//      }
//    }
//    return token;
//  }

    private String generateToken() {
        String token = SysUtil.MD5Digest(UUID.randomUUID().toString());
        return token;
    }

    public List<UserDTO> quickFind(String name) {
        return userReadMapper.quickFind(name);
    }

    public List<UserEmployeeDTO> getUserEmployee(QueryUtil queryUtil) {
        List<UserEmployeeDTO> list = userReadMapper.getUserEmployee(queryUtil);
        return list;
    }

    public List<UserSearchDTO> getAllSearchUser() {
        return userReadMapper.getAllSearchUser();
    }

    public Boolean validate(Object obj) throws BusinessException {
        User user = (User) obj;
        Boolean ret = false;
        if (user == null) {
            throw new BusinessException(ErrorMessageEnum.User_Insert_Or_Update_Empty_Object);
        }

        if (null != user.getPersonalInfo()) {
            if (null != user.getPersonalInfo().getId()) {
                throw new BusinessException(ErrorMessageEnum.User_Insert_Or_Update_Personal_Info_ID_Not_Empty);
            }
        }

        // 判断roleList id存不存在
        if (null != user.getRoleList()) {
            for (int i = 0; i < user.getRoleList().size(); i++) {
                if (roleReadMapper.getRoleIdCount(user.getRoleList().get(i).getId()) == 0) {
                    throw new BusinessException(ErrorMessageEnum.User_Insert_Or_Update_Role_Not_Exist, user.getRoleList().get(i).getId());
                }
            }
        }

        if (null != user.getLoginId() && !StringUtils.isEmpty(user.getLoginId().toString())) {

            //更新
            if (null != user.getId() && !StringUtils.isEmpty(user.getId().toString())) {
                //更新时，用loginId 查出的id 与 现有的id作对比
                User userInfo = userReadMapper.selectByLoginId(user.getLoginId());
                if (userInfo != null) {
                    if (!userInfo.getId().equals(user.getId())) {
                        throw new BusinessException(ErrorMessageEnum.User_CreateUser_LoginID_Already_Exist, user.getLoginId());
                    }
                }

            } else {
                //根据loginId 查询表里存在的数量
                int i = userReadMapper.checkLoginIdUnique(user.getLoginId());

                if (i > 0) {
                    throw new BusinessException(ErrorMessageEnum.User_CreateUser_LoginID_Already_Exist, user.getLoginId());
                }

            }
        }

        ret = true;
        return ret;
    }

    public Boolean validateForUpdate(Object obj) throws BusinessException {

        Boolean ret = validate(obj);
        User user = (User) obj;

        if (user.getId() == null) {
            throw new BusinessException(ErrorMessageEnum.User_UpdateUser_Empty_User_ID);
        }

        if (null != user.getLoginId() && StringUtils.isEmpty(user.getLoginId())) {
            throw new BusinessException(ErrorMessageEnum.User_UpdateUser_Empty_LoginID);
        }

        if (null != user.getPassword() && StringUtils.isEmpty(user.getPassword())) {
            throw new BusinessException(ErrorMessageEnum.User_UpdateUser_Empty_Password);
        }

        if (null != user.getDisabled() && StringUtils.isEmpty(user.getDisabled().toString())) {
            throw new BusinessException(ErrorMessageEnum.User_UpdateUser_Empty_Disabled);
        }

        if (null != user.getLocked() && StringUtils.isEmpty(user.getLocked().toString())) {
            throw new BusinessException(ErrorMessageEnum.User_UpdateUser_Empty_Locked);
        }

        if (null != user.getPersonalInfo()) {
            if (null != user.getPersonalInfo().getEmailPrimary()
                    && StringUtils.isEmpty(user.getPersonalInfo().getEmailPrimary())) {
                throw new BusinessException(ErrorMessageEnum.User_CreateUser_Empty_Email);
            }
        }

        ret = true;
        return ret;

    }


    @Override
    public List<User> getAllUserByRoleId(Integer roleId) {
        return userReadMapper.selectAllUserByRoleId(roleId);
    }

    @Deprecated
    public Boolean validateForDelete(Object obj) throws BusinessException {
        return true;
    }

    @Override
    public void setEnvironment(Environment environment) {
        propertyResolver = new RelaxedPropertyResolver(environment, ENV_FILE_PATH);
    }


    //current + the days of value SYS_PWD_CFG_D_PWD_EXP_DAYS
    private Date getPWDExpiredDate() {

        Double pwdExpDays = configurationService.getDoubleValue(ConfigurationService.SYS_PWD_CFG_D_PWD_EXP_DAYS);
        if (pwdExpDays == null) {
            pwdExpDays = 30 * 3.0;
        }


        return new Date(taskService.getCurrentTime().getTime() + (long) (1000 * 60 * 60 * 24 * pwdExpDays));
    }

    //SYS_PWD_CFG_C_PWD_EXP
    @Override
    public boolean canPWDExpired() {
        Configuration configuration = configurationService.get("SYS_PWD_CFG_C_PWD_EXP");

        if (configuration != null) {
            String canPWDExpired = configuration.getValue();
            if (!StringUtils.isBlank(canPWDExpired) && "Y".equalsIgnoreCase(canPWDExpired)) {
                return true;
            }
        }

        return false;
    }

    @Override
    public boolean isCurrentUserPwdExpired() {
        try {
            User currentUser = (User) this.get(SecurityUtils.getCurrentLogin().getUserId());
            //判断密码是否过期
            if (this.canPWDExpired()) {
                if (currentUser != null) {
                    Date pwdExpiredDate = currentUser.getPwdExpiredDate();
                    if (pwdExpiredDate != null) {
                        Date now = taskService.getCurrentTime();
                        if (now.compareTo(pwdExpiredDate) > 0) {
                            logger.info("the user [" + currentUser.getLoginId() + "] password has expired!");
                            return true;
                        }
                    }
                }
            }
        } catch (BusinessException e) {

        }
        return false;
    }

    @Override
    public Boolean updatePassword(UserPassChangeDTO userPassChangeDTO) {
        Boolean ret = false;
        String old_password = userPassChangeDTO.getOld_password();
        String new_password = userPassChangeDTO.getNew_password();
        User user = userReadMapper.selectByPrimaryKey(userPassChangeDTO.getUser_id());
        String old_password_MD5 = user.getPassword();
        if (old_password != null) {
            if (SysUtil.MD5Digest(old_password).equals(old_password_MD5)) {
                user.updateCommonInfo(userPassChangeDTO.getUser_id());
                user.setPassword(SysUtil.MD5Digest(new_password));
                user.setUpdatePwdFlag(true);
                if (canPWDExpired()) {
                    user.setPwdExpiredDate(getPWDExpiredDate());
                }
                int success = userWriteMapper.updateByPrimaryKeySelective(user);
                if (success == 1)
                    ret = true;
            }
        }
        return ret;
    }

    @Override
    public Integer getT2GUserId() {
        List<User> users = getUsersByRoleCode("_T2G");
        if (!CollectionUtils.isEmpty(users)) {
            return users.get(0).getId();
        }
        return null;
    }

    @Override
    public Integer getT2OUserId() {
        List<User> users = getUsersByRoleCode("_T2O");
        if (!CollectionUtils.isEmpty(users)) {
            return users.get(0).getId();
        }
        return null;
    }

    public List<User> getUsersByRoleCode(String code) {
        return userReadMapper.selectUsersByRoleCode(code);
    }

    @Override
    public Integer getFactoryManagerId(String installVendorId) {
        return userReadMapper.selectFactoryManagerId(installVendorId);
    }

    @Override
    public List<User> getAllUserByOrgID(Integer orgID) {
        return userReadMapper.getAllUserByOrgID(orgID);
    }

    @Override
    public void createWechatUser(UserDTO userDTO) throws Exception {
        WeChatUser user = new WeChatUser();
        try {
            user.setUserid(userDTO.getLogin_id());
            user.setName(userDTO.getLast_name() + userDTO.getFirst_name());
            List<Integer> wechatid = orgReadMapper.getMultiWeChatIds(userDTO.getOrg_ids()); //查询部门对应的微信端id
            user.setDepartment(wechatid.toString());
        } catch (Exception e) {
            logger.error("微信端添加人员参数不完整(登陆名、姓、名、部门id  注：后台查询部门对应的微信端部门id）)", e);
            throw new WechatBusinessException("微信端添加人员参数不完整(登陆名、姓、名、部门id  注：后台查询部门对应的微信端部门id）)");
        }
        if (null != userDTO.getWorkPhoneNumber()) {
            user.setMobile(userDTO.getWorkPhoneNumber());
        } else {
            throw new BusinessException("请输入添加人员手机号");
        }

        if (null != userDTO.getEmail_primary()) {
            user.setEmail(userDTO.getEmail_primary());
        }
        try {
            String result = weChatService.addUser(user);
        } catch (Exception e) {
            throw new WechatBusinessException("后台系统创建人员成功，微信端异常:" + e.getMessage());
        }
    }

    @Override
    public void deleteWechatUsers(List<String> userIDs) throws Exception {
        try {
            String result = weChatService.batchDelete(userIDs);
        } catch (Exception e) {
            logger.error("删除企业微信端成员异常.", e);
            throw new WechatBusinessException("删除企业微信端成员异常:" + e.getMessage());
        }

        try {
            weChatUserLoginWriteMapper.deleteUsers(userIDs);
        } catch (Exception e) {
            logger.error("删除微信成员登陆信息失败", e);
            throw new WechatBusinessException("删除微信成员登陆信息失败" + "   " + this.getClass().toString());
        }
    }

    @Override
    public void updateWechatUserPw(WeChatUserLogin user) {
        try {
            user.setPassword(DESUtil.encrypt(user.getPassword()));
        } catch (UnsupportedEncodingException e) {
            logger.error("updateWechatUserPw error.", e);
        }
        weChatUserLoginWriteMapper.updateByLoginId(user);
    }

    @Override
    public void updateWechatUser(UserPassChangeDTO userPassChangeDTO, User user) {
        // TODO Auto-generated method stub

    }

    @Override
    public List<String> getUserLoginIdsByIds(String userIDs) {
        List<String> loginids = userReadMapper.getUserLoginIdsByIds(userIDs);
        return loginids;
    }

    @Override
    public void updateWechatUser(UserDTO userDTO) throws Exception {
        String userid = null;
        if (userDTO.getId() == null) {
            throw new WechatBusinessException("没有人员id");
        }
        UserDTO user = userReadMapper.getUserDTO(userDTO.getId());
        userid = user.getLogin_id();
        if (userid == null) {
            throw new WechatBusinessException("该人员在为企业微信没有找到对应人员");
        }
        WeChatUser wechatuser = new WeChatUser();
        wechatuser.setUserid(userid);
        if (null != userDTO.getOrg_ids()) {
            List<Integer> wechatid = orgReadMapper.getMultiWeChatIds(userDTO.getOrg_ids());
            wechatuser.setDepartment(wechatid.toString());
        }
        if (null != userDTO.getWorkPhoneNumber()) {
            wechatuser.setMobile(userDTO.getWorkPhoneNumber());
        }
        if (null != userDTO.getEmail_primary()) {
            wechatuser.setEmail(userDTO.getEmail_primary());
        }
        String name = null;
        if (null != userDTO.getFirst_name()) {
            if (null != userDTO.getLast_name()) {//姓名都改了
                name = userDTO.getLast_name() + userDTO.getFirst_name();
            } else {//变名不变姓
                name = user.getLast_name() + userDTO.getFirst_name();
            }
        } else {
            if (null != userDTO.getLast_name()) {//姓变名不变
                name = userDTO.getLast_name() + user.getFirst_name();
            } else {//姓名全没改
                name = user.getLast_name() + user.getFirst_name();
            }
        }
        wechatuser.setName(name);
        try {
            weChatService.updateUser(wechatuser);
        } catch (Exception e) {
            throw new WechatBusinessException("更新企业微信人员异常: " + e.getMessage());
        }

    }

    @Override
    public Boolean updatePasswordByUserId(Integer userId) throws BusinessException {
        int oprUserId = SecurityUtils.getCurrentLogin().getUserId();
        Boolean ret = false;
        //获取系统默认的用户密码
        String newPassword = configurationService.getStringValue(ConfigurationService.SYS_DEFAULT_PASSWORD);
        User user = userReadMapper.selectByPrimaryKey(userId);
        if (user != null && !StringUtils.isEmpty(newPassword)) {
            user.updateCommonInfo(oprUserId);
            user.setPassword(SysUtil.MD5Digest(newPassword));
            if (canPWDExpired()) {
                user.setPwdExpiredDate(getPWDExpiredDate());
            }
            user.setUpdatePwdFlag(false);
            int success = userWriteMapper.updateByPrimaryKeySelective(user);
            if (success == 1) {
                //获取user的手机号码
                if (user.getPersonalInfoId() != null) {
                    //发送短信
                    PersonalInfo personalInfo = personalInfoService.get(user.getPersonalInfoId());
                    String userName = personalInfo.getLastName() + personalInfo.getFirstName();
                    String loginId = user.getLoginId();
                    String params = " {'name':'" + userName + "','account':'" + loginId + "','pwd':'" + newPassword + "'}";
                    //SMS_67171179	您的密码已经重置为${pwd}，请尽快登录系统修改密码。
                    String signName = configurationService.getStringValue(ConfigurationService.SEND_MSG_SIGN_NAME);
                    SMSUtil.sendSms(sendMsgConfiguration.getChangePasswordCode(), personalInfo.getWorkPhoneNumber(), params,signName);
                }
                ret = true;
            }
        } else {
            ret = false;
        }
        return ret;
    }

    @Override
    public HashMap<String, Object> findPhone(String loginId) {
        HashMap<String, Object> map = new HashMap<String, Object>();
        String login = userReadMapper.validateLoginId(loginId);
        if (login != null) {
            String phone = userReadMapper.selectPhoneByLoginId(loginId);
            if (org.apache.commons.lang3.StringUtils.isEmpty(phone)) {
                map.put("status", -2);
                map.put("msg", "该用户没有手机号");
                return map;
            }
            map.put("status", 0);
            map.put("phone", phone);
            return map;
        }
        map.put("status", -1);
        map.put("msg", "账号不存在");
        return map;
    }


    @Override
    public HashMap<String, Object> updateBackPassword(RegisterReq dto) {
        HashMap<String, Object> map = new HashMap<String, Object>();
        String loginId = dto.getLoginId();
        String code = dto.getVerifyCode();
        String password = dto.getPassword();
        String login = userReadMapper.validateLoginId(loginId);
        if (login != null) {
            String phone = userReadMapper.selectPhoneByLoginId(loginId);
            if (StringUtils.isEmpty(phone)) {
                map.put("status", -2);
                map.put("msg", "该用户没有手机号");
                return map;
            }
            try {
                // 校验验证码
                VerificationCode verification = new VerificationCode();
                verification.setCellPhone(phone);
                verification.setVerificationCode(code);
                verification.setOper(SendMsgCodeEnum.updatePsd.getCode());
                sendSmsService.checkVerification(verification);
            } catch (LandseaBusinessException e) {
                map.put("status", -3);
                map.put("msg", "验证码错误！");
                return map;
            }
            //更新密码
//            String pswMd5 = SysUtil.MD5Digest(password);
            userWriteMapper.updatePasswordByLoginId(loginId, password);
            map.put("status", 0);
            return map;
        } else {
            map.put("status", -1);
            map.put("msg", "账号不存在");
            return map;
        }

    }

    @Override
    public UserPrjRoleDTO getPrjsAndRole(Integer userId)
    {
        UserPrjRoleDTO dto = userReadMapper.getPrjsAndRole(userId);
        return dto;
    }

}
